package cn.com.libertymutual.production.utils.ftp;

import it.sauronsoftware.ftp4j.FTPClient;
import it.sauronsoftware.ftp4j.FTPException;
import it.sauronsoftware.ftp4j.FTPFile;

import java.io.File;

/**
 * 
 * @title ftpj4实现的客户端 可以支持jdk 1.6 使用
 * @date 2017年7月27日
 */
public class FTP4JUtil {

    /** 
     * 创建FTP连接 
     * 
     * @param host         主机名或IP 
     * @param port         ftp端口 
     * @param username ftp用户名 
     * @param password ftp密码 
     * @return 一个客户端 
     * @throws Exception 
     */ 
    public static FTPClient makeFtpConnection(String host, int port, String username, String password) throws Exception { 
            FTPClient client = new FTPClient(); 
            try { 
            	
//            	TrustManager[] trustManager = new TrustManager[] { new X509TrustManager() {
//    				public X509Certificate[] getAcceptedIssuers() {
//    					return null;
//    				}
//
//    				public void checkClientTrusted(X509Certificate[] certs,
//    						String authType) {
//    				}
//
//    				public void checkServerTrusted(X509Certificate[] certs,
//    						String authType) {
//    				}
//    			} };
//    			SSLContext sslContext = null;
//    			sslContext = SSLContext.getInstance("SSL");
//    			sslContext.init(null, trustManager, new SecureRandom());
//    			SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
//    			client.setSSLSocketFactory(sslSocketFactory);
//    			client.setSecurity(FTPClient.SECURITY_FTPES);
                client.connect(host, port); 
                client.login(username, password); 
            } catch (Exception e) { 
                    throw new Exception(e); 
            } 
            return client; 
    } 


    
    /** 
     * FTP上传本地文件到FTP的一个目录下 
     * 
     * @param client                     FTP客户端 
     * @param localfile                本地文件 
     * @param remoteFolderPath FTP上传目录 
     */ 
	public static void upload(FTPClient client, File localfile,
			String remoteFolderPath) {
		remoteFolderPath = PathToolkit.formatPath4FTP(remoteFolderPath);
		MyFtpListener listener = MyFtpListener.instance(FTPOptType.UP);
		try {

			if (!localfile.exists())
				throw new RuntimeException("所要上传的FTP文件" + localfile.getPath()
						+ "不存在！");
			if (!localfile.isFile())
				throw new RuntimeException("所要上传的FTP文件" + localfile.getPath()
						+ "是一个文件夹！");
			/*不存在就创建*/
//			if (isExist(client, remoteFolderPath) == -1) {
//				/*多线程判断会有问题，如果异常为 [code=550, message= Directory already exists 则不处理*/
//				try {
//					client.createDirectory(remoteFolderPath);
//				} catch (FTPException e) {
//					String err = e.getMessage();
//					if (!"Directory already exists".equals(err)) {
//						throw new RuntimeException(e);
//					}
//
//				}
//			}
			try {
				client.changeDirectory(remoteFolderPath);
			} catch (FTPException e) {
				client.createDirectory(remoteFolderPath);
				client.changeDirectory(remoteFolderPath);
			}
			if (listener != null) {
				client.upload(localfile, listener);
			} else {
				client.upload(localfile);
			}
		} catch (Exception e) {
			throw new RuntimeException(e);
		} finally {
			closeConnection(client);
		}
	}

    /** 
     * FTP上传本地文件到FTP的一个目录下 
     * 
     * @param client                     FTP客户端 
     * @param localfilepath        本地文件路径 
     * @param remoteFolderPath FTP上传目录 
     */ 
    public static void upload(FTPClient client, String localfilepath, String remoteFolderPath) { 
            File localfile = new File(localfilepath); 
            upload(client, localfile, remoteFolderPath); 
    } 
    
	/**
	 * 判断一个FTP路径是否存在，如果存在返回类型(FTPFile.TYPE_DIRECTORY=1、FTPFile.TYPE_FILE=0、
	 * FTPFile.TYPE_LINK=2) 如果文件不存在，则返回一个-1
	 * 
	 * @param client
	 *            FTP客户端
	 * @param remotePath
	 *            FTP文件或文件夹路径
	 * @return 存在时候返回类型值(文件0，文件夹1，连接2)，不存在则返回-1
	 */
	public static int isExist(FTPClient client, String remotePath) {
		remotePath = PathToolkit.formatPath4FTP(remotePath);
		FTPFile[] list = null;
		try {
			list = client.list(remotePath);
		} catch (Exception e) {
			return -1;
		}
		if (list.length > 1)
			return FTPFile.TYPE_DIRECTORY;
		else if (list.length == 1) {
			FTPFile f = list[0];
			if (f.getType() == FTPFile.TYPE_DIRECTORY)
				return FTPFile.TYPE_DIRECTORY;
			// 假设推理判断
			String _path = remotePath + "/" + f.getName();
			try {
				int y = client.list(_path).length;
				if (y == 1)
					return FTPFile.TYPE_DIRECTORY;
				else
					return FTPFile.TYPE_FILE;
			} catch (Exception e) {
				return FTPFile.TYPE_FILE;
			}
		} else {
			try {
				client.changeDirectory(remotePath);
				return FTPFile.TYPE_DIRECTORY;
			} catch (Exception e) {
				return -1;
			}
		}
	}

	/**
	 * 关闭FTP连接，关闭时候像服务器发送一条关闭命令
	 * 
	 * @param client
	 *            FTP客户端
	 * @return 关闭成功，或者链接已断开，或者链接为null时候返回true，通过两次关闭都失败时候返回false
	 */

	public static boolean closeConnection(FTPClient client) {
		if (client == null)
			return true;
		if (client.isConnected()) {
			try {
				client.disconnect(true);
				return true;
			} catch (Exception e) {
				try {
					client.disconnect(false);
				} catch (Exception e1) {
					e1.printStackTrace();
					return false;
				}
			}
		}
		return true;
	}
	
	/**
	 * 下载
	 * @param client
	 * @param remoteFileName
	 * @param localFolderPath
	 */
	public static void download(FTPClient client, String remoteFileName, String localFolderPath) {

		try {
			client.download(remoteFileName, new File(localFolderPath + File.separator + new File(remoteFileName).getName()));
		} catch (Exception e) {

			e.printStackTrace();
		} finally {
			closeConnection(client);
		}

	}
}
